home *** CD-ROM | disk | FTP | other *** search
/ Nautilus 1992 July / Nautilus-3-8 / Nautilus-3-8.bin / Tools & Utilities / Techy Stuff / Source ƒ / ASM 2.0 ƒ / do.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-06-15  |  26.4 KB  |  1,266 lines

  1. #include <stdio.h>
  2. #include <ctype.h>
  3. #include "as.h"
  4. #include "table.h"
  5. #include "lookup.h"
  6. #include "regs.h"
  7.  
  8. #define    cpid(x)    ((x)<<9)    /* coprocessor id field */
  9.  
  10. #ifdef PMMU
  11. int     Ppid    = cpid(0);    /* PMMU coprocessor ID */
  12. #endif
  13.  
  14. extern int Size;
  15. extern char Label[];
  16. extern char Line[];
  17. extern char *Optr;
  18. extern int Pc;
  19. extern int Lflag;
  20. extern int Fwdsize;
  21. extern int Old_pc;
  22. extern int P_total;
  23. extern int P_force;
  24. char *next_str();
  25.  
  26. struct opts {   /* a list of allowed options */
  27.     char    *opt_name;
  28.     int     (*opt_func)();
  29.     };
  30.  
  31. int o_list(),o_nolist(),o_null();
  32.  
  33. struct opts opt_list[] = {
  34.     "l",            o_list,
  35.     "list",         o_list,
  36.     "nol",          o_nolist,
  37.     "nolist",       o_nolist,
  38.     "brl",          o_null,
  39.     0,              0
  40.     };
  41.  
  42. #ifdef FLOAT
  43.  
  44. int     Fpid    = cpid(1);    /* floating point coprocessor ID */
  45. int o_fpid(),o_round(),o_prec();
  46.  
  47. struct opts fopt_list[] = {
  48.     "id",           o_fpid,
  49.     "round",        o_round,
  50.     "prec",         o_prec,
  51.     0,              0
  52.     };
  53. #endif
  54.  
  55. /* range checking categories */
  56. #define UBYTE   0       /* unsigned byte */
  57. #define SBYTE   1       /* signed byte */
  58. #define XBYTE   2       /* extended byte */
  59. #define UWORD   3       /* unsigned word */
  60. #define SWORD   4       /* signed word */
  61. #define XWORD   5       /* extended word */
  62. #define QUK     6       /* quick value 1-8 */
  63. #define LOW3    7       /* 3 bit field */
  64. #define LOW4    8       /* 4 */
  65. #define LOW5    9       /* 5 */
  66. #define    LOW6    10    /* 6 */
  67. #define LOW7    11      /* 7 */
  68. #define LOW7S   12      /* 7, signed */
  69.  
  70. struct ranges {
  71.     int     r_min;  /* minimum value allowed */
  72.     int     r_max;  /* max. allowed */
  73.     int     r_mask; /* return value mask */
  74.     };
  75.  
  76. struct ranges ckrange[] = {
  77.     0,      MAXUBYTE,       0x00FF,
  78.     MINBYTE,MAXBYTE,        0x00FF,
  79.     MINBYTE,MAXUBYTE,       0x00FF,
  80.     0,      MAXUWORD,       0xFFFF,
  81.     MINWORD,MAXWORD,        0xFFFF,
  82.     MINWORD,MAXUWORD,       0xFFFF,
  83.     1,      8,              0x0007,
  84.     0,      7,              0x0007,
  85.     0,      15,             0x000F,
  86.     0,      31,             0x001F,
  87.     0,    63,        0x003F,
  88.     0,      127,            0x007F,
  89.     -64,    63,             0x007F,
  90.     };
  91.  
  92. /*
  93.  *      localinit --- machine specific initialization
  94.  */
  95. localinit()
  96. {
  97.     register struct regs *r;
  98.  
  99.     /* install register names in symbol table */
  100.     for(r=iregs; r<&iregs[NIREGS]; r++)
  101.         install(r->r_name,r->r_value,r->r_type);
  102. }
  103.  
  104. /*
  105.  *      do_op --- process mnemonic
  106.  */
  107. do_op(class,op,op2)
  108. int class;    /* mnemonic class */
  109. int op;         /* base opcode */
  110. int op2;        /* second opcode (e.g. F-lines) */
  111. {
  112.     extern struct ea Eas[];
  113.     register struct ea *ea1 = &Eas[0];
  114.     register struct ea *ea2 = &Eas[1];
  115.     register struct ea *ea3 = &Eas[2];
  116.     register struct ea *ea4 = &Eas[3];
  117.     register int tmp;
  118.     register int dist;      /* distance on branches */
  119.     register int rlist;     /* bit map of register list */
  120.     char    *ptmp;
  121.  
  122.     switch(class){
  123.     case INH:               /* inherent */
  124.         eword(op);
  125.         break;
  126.  
  127.     case RXRY:              /* Rx and Ry, no size */
  128.         eword( op + (ea2->reg<<9) + ea1->reg );
  129.         break;
  130.  
  131.     case RXRYS:             /* Rx and Ry, sized */
  132.         eword( op + (ea2->reg<<9) + size76() + ea1->reg );
  133.         break;
  134.  
  135.     case RXRYR:             /* Rx and Ry, reversed */
  136.         eword( op + (ea1->reg<<9) + ea2->reg );
  137.         break;
  138.  
  139.     case RXRYP:             /* Rx and Ry, pack/unpack */
  140.         eword( op + (ea2->reg<<9) + ea1->reg );
  141.         eword(check(ea3->const,UWORD));
  142.         break;
  143.  
  144.     case EAREG:             /* ea to register */
  145.         eword( op + (ea2->reg<<9) + modreg(ea1) );
  146.         finish(ea1);
  147.         break;
  148.  
  149.     case EAREGS:            /* ea to register, sized */
  150.         eword( op + (ea2->reg<<9) + size76() + modreg(ea1));
  151.         finish(ea1);
  152.         break;
  153.  
  154.     case REGEA:             /* register to ea */
  155.         eword( op + (ea1->reg<<9) + modreg(ea2));
  156.         finish(ea2);
  157.         break;
  158.  
  159.     case REGEAS:            /* register to ea, signed */
  160.         eword( op + (ea1->reg<<9) + size76() + modreg(ea2));
  161.         finish(ea2);
  162.         break;
  163.  
  164.     case IMMEAS:            /* immediate to ea, sized */
  165.         eword( op + size76() + modreg(ea2) );
  166.         if(Size==L)
  167.             elong(ea1->const);
  168.         else
  169.             eword(ea1->const);
  170.         finish(ea2);
  171.         break;
  172.  
  173.     case QUKEA:             /* quick immediate to ea */
  174.         if( (Size&B) && ea2->type==AN )
  175.             error("Byte not allowed to address reg.");
  176.         eword( op + (check(ea1->const,QUK)<<9) + size76() + modreg(ea2) );
  177.         finish(ea2);
  178.         break;
  179.  
  180.     case IMMB:              /* immediate byte */
  181.         eword(op);
  182.         eword(check(ea1->const,UBYTE));
  183.         break;
  184.  
  185.     case IMMW:              /* immediate word */
  186.         eword(op);
  187.         eword(check(ea1->const,XWORD));
  188.         break;
  189.  
  190.     case IMMWS:             /* immediate word, signed */
  191.         eword(op);
  192.         eword(check(ea1->const,SWORD));
  193.         break;
  194.  
  195.     case IMM3:              /* immediate value, 3 bits */
  196.         eword( op + check(ea1->const,LOW3) );
  197.         break;
  198.  
  199.     case IMM4:              /* immediate value, 4 bits */
  200.         eword( op + check(ea1->const,LOW4) );
  201.         break;
  202.  
  203.     case RSHIFT:            /* register shift */
  204.         eword( op + (ea1->reg<<9) + size76() + ea2->reg );
  205.         break;
  206.  
  207.     case QSHIFT:            /* immediate (quick fmt) shift */
  208.         eword( op + (check(ea1->const,QUK)<<9) + size76() + ea2->reg);
  209.         break;
  210.  
  211.     case EA:                /* ea */
  212.         eword( op + modreg(ea1) );
  213.         finish(ea1);
  214.         break;
  215.  
  216.     case EAREV:             /* ea, reversed */
  217.         eword( op + modreg(ea2) );
  218.         finish(ea2);
  219.         break;
  220.  
  221.     case EAS:               /* ea, sized */
  222.         eword( op + size76() + modreg(ea1) );
  223.         finish(ea1);
  224.         break;
  225.  
  226.     case BCC:               /* conditional branches */
  227.         dist = ea1->const - (Pc+2);
  228.         if(Size==U && ea1->force )
  229.             Size = Fwdsize;
  230.         if(Size==U){
  231.             if( dist<MINWORD || dist>MAXWORD )
  232.                 Size = L;
  233.             else if( dist<MINBYTE || dist>MAXBYTE)
  234.                 Size = W;
  235.             else
  236.                 Size = B;
  237.             }
  238.         switch(Size){
  239.         case B:
  240.             if( dist==0 || dist== -1)
  241.                 error("Bad branch destination");
  242.             eword( op + check(dist,SBYTE) );
  243.             break;
  244.         case W:
  245.             eword(op);
  246.             eword(check(dist,SWORD));
  247.             break;
  248.         case L:
  249.             eword(op+0xFF);
  250.             elong(dist);
  251.             break;
  252.             }
  253.         break;
  254.  
  255.     case BIT:               /* single bit manipulation */
  256.         eword( op + modreg(ea2) );
  257.         eword( check(ea1->const,LOW5) );
  258.         finish(ea2);
  259.         break;
  260.  
  261.     case BITFLD:            /* bit fields */
  262.         eword( op + modreg(ea1) );
  263.         eword( bitfld(ea2,0) );        /* {Dn/#:Dn/#} formatted word */
  264.         finish(ea1);
  265.         break;
  266.  
  267.     case BITFLD2:           /* bit fields, second format */
  268.         if( ea2->type == FIELD ){
  269.             eword( op + modreg(ea1) );
  270.             eword( bitfld(ea2,ea3->reg) ); /* {Dn/#:Dn/#} formatted word */
  271.             finish(ea1);
  272.             }
  273.         else{   /* bfins is backwards */
  274.             eword( op + modreg(ea2) );
  275.             eword( bitfld(ea3,ea1->reg) ); /* {Dn/#:Dn/#} formatted word */
  276.             finish(ea2);
  277.             }
  278.         break;
  279.  
  280.     case CALLM:             /* callm */
  281.         eword( op + modreg(ea2) );
  282.         eword(check(ea1->const,UBYTE));
  283.         finish(ea2);
  284.         break;
  285.  
  286.     case CAS:               /* cas */
  287.         eword( op + size109b() + modreg(ea3) );
  288.         eword( (ea2->reg<<6) + ea1->reg );
  289.         finish(ea3);
  290.         break;
  291.  
  292.     case CAS2:              /* cas2 */
  293.         eword( op + size109b() );
  294.         if(ea3->stat)
  295.             ea3->reg += 8;
  296.         eword( (ea3->reg<<12) + (ea2->reg<<6) + ea1->reg);
  297.         if(ea3->stat2)
  298.             ea3->reg2 += 8;
  299.         eword( (ea3->reg2<<12) + (ea2->reg2<<6) + ea1->reg2);
  300.         break;
  301.  
  302.     case CHK:               /* chk */
  303.         if( Size != L )
  304.             op |= 0x0080;
  305.         eword( op + (ea2->reg<<9) + modreg(ea1) );
  306.         finish(ea1);
  307.         break;
  308.  
  309.     case CHK2:              /* chk2,cmp2 */
  310.         eword( op + size109() + modreg(ea1) );
  311.         eword( op2 + adreg(ea2) );
  312.         finish(ea1);
  313.         break;
  314.  
  315.     case DBCC:              /* dbcc */
  316.         dist = ea2->const - (Old_pc+2);
  317.         eword(op + ea1->reg );
  318.         eword(check(dist,SWORD));
  319.         break;
  320.  
  321.     case MULDIV:            /* multiplies and divides */
  322.         eword( op + modreg(ea1) );
  323.         if( ea2->type == DN )
  324.             ea2->reg2 = ea2->reg;
  325.         eword( op2 + (ea2->reg2<<12) + ea2->reg);
  326.         finish(ea1);
  327.         break;
  328.  
  329.     case REG:               /* register */
  330.         eword(op + ea1->reg);
  331.         break;
  332.  
  333.     case MOVEU:             /* move to/from USP */
  334.         if( ea1->type == CN ){
  335.             if( ea1->reg != USP )
  336.                 error("USP Required");
  337.             eword( op + ea2->reg);
  338.             }
  339.         else{
  340.             if( ea2->reg != USP )
  341.                 error("USP Required");
  342.             eword( op + ea1->reg);
  343.             }
  344.         break;
  345.  
  346.     case REGIMM:            /* register with immediate */
  347.         eword(op + ea1->reg);
  348.         if( Size == L)
  349.             elong(ea2->const);
  350.         else
  351.             eword(ea2->const);
  352.         break;
  353.  
  354.     case MOVE:              /* move */
  355.         tmp = modreg(ea2);
  356.         tmp = ((tmp&7)<<3) + ((tmp>>3)&7);      /* reverse modreg */
  357.         eword( op + (tmp<<6) + modreg(ea1) );
  358.         finish(ea1);
  359.         finish(ea2);
  360.         break;
  361.  
  362.     case MOVEC:             /* movec */
  363.         eword(op);
  364.         if( ea1->type == CN )
  365.             eword( adreg(ea2) + ea1->reg );
  366.         else
  367.             eword( adreg(ea1) + ea2->reg );
  368.         break;
  369.  
  370.     case MOVEQ:             /* move quick */
  371.         eword(op + (ea2->reg<<9) + check(ea1->const,SBYTE) );
  372.         break;
  373.  
  374.     case MOVEMO:            /* movem register to memory */
  375.         if(ea1->type == IMMED)
  376.             rlist = ea1->const;
  377.         else
  378.             rlist = getrlist(ea1);
  379.         if( ea2->type == PREDEC )
  380.             rlist = reverse(rlist)>>16;    /* assumes int=32bits */
  381.         eword( op + modreg(ea2) );
  382.         eword(rlist);
  383.         finish(ea2);
  384.         break;
  385.  
  386.     case MOVEMI:            /* movem memory to register */
  387.         if(ea2->type == IMMED)
  388.             rlist = ea2->const;
  389.         else
  390.             rlist = getrlist(ea2);
  391.         /* predec not possible here */
  392.         eword(op + modreg(ea1));
  393.         eword(rlist);
  394.         finish(ea1);
  395.         break;
  396.  
  397.     case MOVEPO:            /* movep out */
  398.         if(ea2->itype != D16AN )
  399.             error("Simple indexing only");
  400.         eword(op + (ea1->reg<<9) + ea2->reg);   /* NOT modreg(ea2) */
  401.         finish(ea2);
  402.         break;
  403.  
  404.     case MOVEPI:            /* movep in */
  405.         if(ea1->itype != D16AN )
  406.             error("Simple indexing only");
  407.         eword(op + (ea2->reg<<9) + ea1->reg);   /* NOT modreg(ea1) */
  408.         finish(ea1);
  409.         break;
  410.  
  411.     case MOVES:             /* moves */
  412.         op += size76();
  413.         if( ea1->type == DN || ea1->type == AN ){
  414.             eword( op + modreg(ea2) );
  415.             eword( op2 + adreg(ea1) );
  416.             finish(ea2);
  417.             }
  418.         else{
  419.             eword( op + modreg(ea1) );
  420.             eword( op2 + adreg(ea2) );
  421.             finish(ea1);
  422.             }
  423.         break;
  424.  
  425.     case TRAPCC:            /* trapcc */
  426.         eword(op + (Size==W ? 2 : 3));
  427.         if( Size == L )
  428.             elong(ea1->const);
  429.         else
  430.             eword(check(ea1->const,UWORD));
  431.         break;
  432.  
  433. #ifdef FLOAT
  434.     case FINH:              /* floating inherent */
  435.         eword( op + Fpid );
  436.         eword( op2 );
  437.         break;
  438.  
  439.     case FEAREG:            /* floating ea to regiser */
  440.         fsizchk(ea1);
  441.         eword( op + Fpid + modreg(ea1) );
  442.         eword( op2 + fsize() + (ea2->reg<<7) );
  443.         finish(ea1);
  444.         break;
  445.  
  446.     case FREGREG:           /* floating register to register */
  447.         eword( op + Fpid );
  448.         eword( op2 + (ea1->reg<<10) + (ea2->reg<<7) );
  449.         break;
  450.  
  451.     case FMONAD:            /* floating register (monadic) */
  452.         eword( op + Fpid );
  453.         eword( op2 + (ea1->reg<<10) + (ea1->reg<<7) );
  454.         break;
  455.  
  456.     case FBCC:              /* floating branch */
  457.         eword( op + Fpid + (Size==L ? 0x40 : 0) );
  458.         dist = ea1->const - Pc;
  459.         if( Size == L )
  460.             elong(dist);
  461.         else
  462.             eword(check(dist,SWORD));
  463.         break;
  464.  
  465.     case FDBCC:             /* floating dbcc */
  466.         eword( op + Fpid + ea1->reg);
  467.         eword( op2 );
  468.         dist = ea2->const - Pc;
  469.         eword(check(dist,SWORD));
  470.         break;
  471.  
  472.     case FEA:               /* floating ea */
  473.         eword( op + Fpid + modreg(ea1) );
  474.         finish(ea1);
  475.         break;
  476.  
  477.     case FSCC:              /* floating scc */
  478.         eword( op + Fpid + modreg(ea1) );
  479.         eword(op2);
  480.         finish(ea1);
  481.         break;
  482.  
  483.     case FEAPAIR:           /* floating ea to floating reg pair */
  484.         fsizchk(ea1);
  485.         eword( op + Fpid + modreg(ea1) );
  486.         eword( op2 + fsize() + (ea2->reg<<7) + ea2->reg2);
  487.         finish(ea1);
  488.         break;
  489.  
  490.     case FREGPAIR:          /* floating register to floating reg pair */
  491.         eword( op + Fpid );
  492.         eword( op2 + (ea1->reg<<10) + (ea2->reg<<7) + ea2->reg2);
  493.         break;
  494.  
  495.     case FTSTEA:            /* floating test of ea */
  496.         fsizchk(ea1);
  497.         eword( op + Fpid + modreg(ea1) );
  498.         eword( op2 + fsize() );
  499.         finish(ea1);
  500.         break;
  501.  
  502.     case FTSTREG:           /* floating test of register */
  503.         eword( op + Fpid );
  504.         eword( op2 + (ea1->reg<<10) );
  505.         break;
  506.  
  507.     case FMOVE:             /* floating move */
  508.         fsizchk(ea2);
  509.         eword( op + Fpid + modreg(ea2) );
  510.         if( ea3->type==EMPTY )
  511.             eword( op2 + fsize() + (ea1->reg<<7) );
  512.         else if(ea3->type==DYNK)
  513.             eword( op2 + (ea1->reg<<7) + (ea3->reg<<3));
  514.         else if(ea3->type==STATK)
  515.             eword( op2 + (ea1->reg<<7) + check(ea3->const,LOW7S) );
  516.         else
  517.             fatal("Botch in FMOVE");
  518.         finish(ea2);
  519.         break;
  520.  
  521.     case FMOVECR:           /* floating move constant rom */
  522.         eword(op + Fpid);
  523.         eword( op2 + (ea2->reg<<7) + check(ea1->const,LOW7) );
  524.         break;
  525.  
  526.     case FMOVEMI:           /* floating move memory to registers */
  527.         /* predec not possible */
  528.         eword( op + Fpid + modreg(ea1) );
  529.         if( ea2->type == DN )
  530.             ea2->reg <<= 4;
  531.         eword(op2 + ea2->reg);
  532.         finish(ea1);
  533.         break;
  534.  
  535.     case FMOVEMO:           /* floating move registers to memory */
  536.         if (ea2->type != PREDEC )
  537.             op2 += 0x1000;
  538.         if( ea1->type == FLIST && ea2->type==PREDEC )
  539.             ea1->reg = (reverse(ea1->reg)>>24)&0xFF;
  540.         if(ea1->type == DN )
  541.             ea1->reg <<= 4;
  542.         eword(op + Fpid + modreg(ea2));
  543.         eword(op2 + ea1->reg);
  544.         finish(ea2);
  545.         break;
  546.  
  547.     case FMOVEMCI:          /* floating move memory to control regs */
  548.         checkfclist(ea2->reg,ea1);
  549.         eword(op + Fpid + modreg(ea1));
  550.         eword(op2 + ea2->reg );
  551.         finish(ea1);
  552.         break;
  553.  
  554.     case FMOVEMCO:          /* floating move control regs to memory */
  555.         checkfclist(ea1->reg,ea2);
  556.         eword(op + Fpid + modreg(ea2));
  557.         eword(op2 + ea1->reg );
  558.         finish(ea2);
  559.         break;
  560.  
  561.     case FTRAPCC:           /* floating trap on condition */
  562.         eword(op + Fpid + (Size==W ? 2 : 3 ));
  563.         eword(op2);
  564.         if( Size == L )
  565.             elong(ea1->const);
  566.         else
  567.             eword(check(ea1->const,UWORD));
  568.         break;
  569.  
  570.     case FEQU:              /* floating point equate */
  571.         warn("Not implemented");
  572.         break;
  573.  
  574.     case FOPT:              /* floating point option set */
  575.         do_opt(fopt_list);
  576.         break;
  577. #endif
  578.  
  579. #ifdef PMMU
  580.     case PINH:              /* PMMU inherent */
  581.         eword( op + Ppid );
  582.         eword( op2 );
  583.         break;
  584.  
  585.     case PBCC:              /* PMMU branch */
  586.         eword( op + Ppid + (Size==L ? 0x40 : 0) );
  587.         dist = ea1->const - Pc;
  588.         if( Size == L )
  589.             elong(dist);
  590.         else
  591.             eword(check(dist,SWORD));
  592.         break;
  593.  
  594.     case PDBCC:             /* PMMU dbcc */
  595.         eword( op + Ppid + ea1->reg);
  596.         eword( op2 );
  597.         dist = ea2->const - Pc;
  598.         eword(check(dist,SWORD));
  599.         break;
  600.  
  601.     case PFLUSH:            /* PFLUSH, PFLUSHG */
  602.         if( ea3->type != EMPTY )
  603.             op += modreg(ea3);
  604.         eword( op + Ppid );
  605.         eword( op2 + (check(ea2->const,LOW4)<<5) + pmmu_fc(ea1) );
  606.         if(ea3->type != EMPTY)
  607.             finish(ea3);
  608.         break;
  609.  
  610.     case PEA:               /* PMMU with single EA */
  611.         eword(op + Ppid + modreg(ea1));
  612.         finish(ea1);
  613.         break;
  614.  
  615.     case PLOAD:             /* PMMU load ATC entry */
  616.         eword(op + Ppid + modreg(ea2));
  617.         eword(op2 + pmmu_fc(ea1));
  618.         finish(ea2);
  619.         break;
  620.  
  621.     case PMOVEIF:           /* pmove, with no flush of ATC */
  622.         switch(ea2->reg){
  623.         case SRP:
  624.         case CRP:
  625.         case TT0:
  626.         case TT1:
  627.         case TC:
  628.             break;
  629.         default:
  630.             error("Illegal register for pmovef");
  631.             }
  632.         /* FALL THROUGH */
  633.  
  634.     case PMOVEI:            /* PMMU load control reg */
  635.         switch(ea2->reg){
  636.         case CRP:
  637.         case SRP:
  638.         case DRP:
  639.             if( ea2->type == DN )
  640.                 error("Reg. size mismatch");
  641.             break;
  642.         case PCSR:
  643.             error("Read only register");
  644.             break;
  645.             }
  646.         eword(op + Ppid + modreg(ea1));
  647.         eword(op2 + ea2->reg );
  648.         finish(ea1);
  649.         break;
  650.  
  651.     case PMOVEO:            /* PMMU store control reg */
  652.         switch(ea1->reg){
  653.         case CRP:
  654.         case SRP:
  655.         case DRP:
  656.             if( ea2->type == DN )
  657.                 error("Reg. size mismatch");
  658.             break;
  659.             }
  660.         eword(op + Ppid + modreg(ea2));
  661.         eword(op2 + ea1->reg );
  662.         finish(ea2);
  663.         break;
  664.  
  665.     case PSCC:              /* PMMU set on condition (also pflushr) */
  666.         eword( op + Ppid + modreg(ea1));
  667.         eword(op2);
  668.         finish(ea1);
  669.         break;
  670.  
  671.     case PTEST:             /* PMMU test logical address */
  672.         eword( op + Ppid + modreg(ea2));
  673.         if( ea4->type == AN )
  674.             op2 += (ea4->reg+8)<<5;
  675.         eword( op2 + (check(ea3->const,LOW3)<<10) + pmmu_fc(ea1) );
  676.         finish(ea2);
  677.         break;
  678.  
  679.     case PTRAPCC:           /* PMMU trap on condition */
  680.         eword(op + Ppid + (Size==W ? 2 : 3 ));
  681.         eword(op2);
  682.         if( Size == L )
  683.             elong(ea1->const);
  684.         else
  685.             eword(check(ea1->const,UWORD));
  686.         break;
  687.  
  688.     case PVALID:            /* PMMU validate a pointer */
  689.         eword(op + Ppid + modreg(ea2) );
  690.         if( ea1->type == AN )
  691.             eword( op2 + ea1->reg);
  692.         else
  693.             eword(op2);
  694.         finish(ea2);
  695.         break;
  696. #endif
  697.  
  698. #ifdef COPROC
  699.     case CPINH:             /* co-processor inherent */
  700.         eword( op + cpid(ea1->const) );
  701.         eword( check(ea2->const,LOW6) );
  702.         break;
  703.  
  704.     case CPBCC:             /* co-processor branch on condition */
  705.         eword( op + cpid(ea1->const)
  706.               + (Size==L ? 0x40 : 0)
  707.               + check(ea2->const,LOW6) );
  708.         dist = ea3->const - Pc;
  709.         if( Size == L )
  710.             elong(dist);
  711.         else
  712.             eword(check(dist,SWORD));
  713.         break;
  714.  
  715.     case CPDBCC:            /* co-processor dec & branch */
  716.         eword( op + cpid(ea1->const) + ea2->reg);
  717.         eword( check(ea2->const,LOW6) );
  718.         dist = ea3->const - Pc;
  719.         eword(check(dist,SWORD));
  720.         break;
  721.  
  722.     case CPGEN:             /* co-processor generic */
  723.         eword(op + cpid(ea1->const) + modreg(ea3));
  724.         eword( ea2->const );
  725.         finish(ea3);
  726.         break;
  727.  
  728.     case CPEA:              /* co-processor, 1 ea (save/restore) */
  729.         eword(op + cpid(ea1->const) + modreg(ea2));
  730.         finish(ea2);
  731.         break;
  732.  
  733.     case CPSCC:             /* co-processor set on condition */
  734.         eword(op + cpid(ea1->const) + modreg(ea3));
  735.         eword( check(ea2->const,LOW6) );
  736.         finish(ea3);
  737.         break;
  738.  
  739.     case CPTRAPCC:          /* co-processor trap on condition */
  740.         eword(op + cpid(ea1->const) + (Size==W ? 2 : 3 ));
  741.         eword( check(ea2->const,LOW6) );
  742.         if( Size == L )
  743.             elong(ea3->const);
  744.         else
  745.             eword(check(ea3->const,UWORD));
  746.         break;
  747. #endif
  748.  
  749. #ifdef PSEUDO
  750.     case EQU:               /* equate */
  751.         if(*Label){
  752.             install(Label,ea1->const,SYM);
  753.             Old_pc = ea1->const;    /* override normal */
  754.             P_force++;
  755.             }
  756.         else
  757.             error("EQU requires label");
  758.         break;
  759.  
  760.     case DC:                /* define constants */
  761.         while(ea1->type != EMPTY ){
  762.             if( ea1->type == EXPR){
  763.                 switch(Size){
  764.                 case B: emit(ea1->const); break;
  765.                 case U:
  766.                 case W: eword(ea1->const); break;
  767.                 case L: elong(ea1->const); break;
  768.                     }
  769.                 }
  770.             else{   /* must be STRING */
  771.                 ptmp = (char *)ea1->const;
  772.                 switch(Size){
  773.                 case B: while(*ptmp)emit(*ptmp++); break;
  774.                 case U:
  775.                 case W: while(*ptmp)eword(*ptmp++); break;
  776.                 case L: while(*ptmp)elong(*ptmp++); break;
  777.                     }
  778.                 free(ea1->const);
  779.                 }
  780.             ea1++;
  781.             }
  782.         break;
  783.  
  784.     case OPT:               /* assembler options */
  785.         do_opt(opt_list);
  786.         break;
  787.  
  788.     case RORG:              /* relocatable org */
  789.         warn("ORG assumed");
  790.     case ORG:               /* origin */
  791.         Old_pc = Pc = ea1->const;
  792.         f_record();     /* flush out any bytes */
  793.         P_force++;
  794.         break;
  795.  
  796.     case DS:                /* define storage */
  797.         switch(Size){
  798.         case B: tmp = 1; break;
  799.         case U:
  800.         case W: tmp = 2; break;
  801.         case L:
  802.         case S: tmp = 4; break;
  803.         case D: tmp = 8; break;
  804.         case X:
  805.         case P: tmp = 12; break;
  806.             }
  807.         if(ea1->const){
  808.             tmp *= ea1->const;
  809.             while(tmp--)
  810.                 emit(0);
  811.             break;
  812.             }
  813.         ea1->const = tmp;       /* #items was zero, implies align */
  814.         /* fall through to align code */
  815.  
  816.     case ALIGN:                     /* align Pc to boundary */
  817.         if(ea1->const && (tmp=Pc%ea1->const)){
  818.             tmp = ea1->const - tmp;
  819.             while(tmp--)
  820.                 emit(0);
  821.             }
  822.         break;
  823.  
  824.     case INCLUDE:           /* process include file */
  825.         make_pass(next_str());
  826.         P_force = P_total = 0;
  827.         Line[0] = '\n';
  828.         break;
  829.  
  830.     case NULL_OP:           /* ignored mnemonic */
  831.         break;
  832. #endif
  833.  
  834. #ifdef M68HC16
  835.     case LPSTOP:        /* lpstop */
  836.         eword(op);
  837.         eword(op2);
  838.         eword(check(ea1->const,UWORD));
  839.         break;
  840.  
  841.     case TABEA:        /* table, tablenr (ea) */
  842.         eword( op  + modreg(ea1) );
  843.         eword( op2 +  adreg(ea2) + size76() );
  844.         finish(ea1);
  845.         break;
  846.  
  847.     case TABREG:        /* table, tablenr (register pair) */
  848.         eword( op + ea1->reg );
  849.         eword( op2 + adreg(ea2) + size76() + ea1->reg2 );
  850.         break;
  851. #endif
  852.  
  853.     default:
  854.         fatal("Error in Mnemonic table");
  855.         }
  856. }
  857.  
  858. /*
  859.  *      fsizchk --- check that size of instruction matches src/dst
  860.  */
  861. fsizchk(e)
  862. struct ea *e;
  863. {
  864.     if( (Size&(D|X|P)) && e->type==DN )
  865.         error("Bad size");
  866. }
  867.  
  868. /*
  869.  *      check --- verify that constant is within bounds
  870.  */
  871. check(const,type)
  872. int const;
  873. int type;
  874. {
  875.     char    cbuf[100];
  876.     int     lo,hi;
  877.     extern int Pass;
  878.  
  879.     if( Pass==2 ){
  880.         lo = ckrange[type].r_min;
  881.         hi = ckrange[type].r_max;
  882.         if( const<lo || const>hi ){
  883.             sprintf(cbuf,"Value not in range: [%d,%d]",lo,hi);
  884.             warn(cbuf);
  885.             }
  886.         }
  887.     return(const&ckrange[type].r_mask);
  888. }
  889.  
  890. /*
  891.  *      size76 --- compute opcode bits 7 and 6 from Size specifier
  892.  */
  893. size76()
  894. {
  895.     int s=0;
  896.  
  897.     switch(Size){
  898.     case B: s = 0x00; break;
  899.     case W:
  900.     case U: s = 0x40; break;
  901.     case L: s = 0x80; break;
  902.     default:
  903.         fatal("Bad size in size76");
  904.         }
  905.     return(s);
  906. }
  907.  
  908. /*
  909.  *      size109 --- compute opcode bits 10 and 9 from size specifier
  910.  */
  911. size109()
  912. {
  913.     int s=0;
  914.  
  915.     switch(Size){
  916.     case B: s = 0x000; break;
  917.     case W:
  918.     case U: s = 0x200; break;
  919.     case L: s = 0x400; break;
  920.     default:
  921.         fatal("Bad size in size109");
  922.         }
  923.     return(s);
  924. }
  925.  
  926. /*
  927.  *      size109b --- compute opcode bits 10 and 9 from size specifier (alternate)
  928.  */
  929. size109b()
  930. {
  931.     int s = 0;
  932.  
  933.     switch(Size){
  934.     case B: s = 0x200; break;
  935.     case W:
  936.     case U: s = 0x400; break;
  937.     case L: s = 0x600; break;
  938.     default:
  939.         fatal("Bad size in size109b");
  940.         }
  941.     return(s);
  942. }
  943.  
  944. /*
  945.  *      adreg --- return 4 bit encoding for An or Dn (shift left by 12)
  946.  */
  947. adreg(e)
  948. struct ea *e;
  949. {
  950.     int r = e->reg;
  951.  
  952.     if( e->type == AN )
  953.         r += 8;
  954.     return( r<<12);
  955. }
  956.  
  957. /*
  958.  *    modreg --- generate mode/register field from ea structure
  959.  *
  960.  *    return is a 6-bit field suitable for adding to a base
  961.  *    opcode.
  962.  */
  963. modreg(e)
  964. register struct ea *e;
  965. {
  966.     register int mr = 0;
  967.  
  968.     switch(e->type){
  969.     case DN:        mr = 000 + e->reg; break;
  970.     case AN:        mr = 010 + e->reg; break;
  971.     case ANI:       mr = 020 + e->reg; break;
  972.     case PSTINC:    mr = 030 + e->reg; break;
  973.     case PREDEC:    mr = 040 + e->reg; break;
  974.     case INDEX:     mr = e->itype == D16AN ? 050+e->reg : 060+e->reg; break;
  975.     case IMMED:     mr = 074; break;
  976.     case EXPR:      mr = e->siz==L ? 071 : 070; break;
  977.     case PCINDEX:   mr = e->itype == D16AN ? 072 : 073; break;
  978.     default:
  979.         fatal("Bad type in modreg");
  980.         }
  981.     return(mr);
  982. }
  983.  
  984. /*
  985.  *      finish --- generate post-words for an instruction
  986.  */
  987. finish(e)
  988. struct ea *e;
  989. {
  990.     switch(e->type){
  991.     case DN:
  992.     case AN:
  993.     case ANI:
  994.     case PSTINC:
  995.     case PREDEC:
  996.         break;
  997.     case PCINDEX:
  998.         e->const -= Pc;
  999.     case INDEX:
  1000.         switch(e->itype){
  1001.         case D16AN:
  1002.             eword(check(e->const,SWORD));
  1003.             break;
  1004.         case BRIEF:
  1005.             eword( genxreg(e) + check(e->const,SBYTE));
  1006.             break;
  1007.         case FULL:
  1008.             if( e->xn_sup && e->prepst ) /* reserved combination */
  1009.                 e->prepst = 0;
  1010.             eword( genxreg(e) + 0x100 + (e->br_sup<<7) +
  1011.                    (e->xn_sup<<6) + (e->bdsiz<<4) +
  1012.                    (e->prepst<<2) + e->odsiz );
  1013.             switch( e->bdsiz ){
  1014.             case 1:
  1015.                 break;  /* supressed */
  1016.             case 2:
  1017.                 eword(check(e->const,SWORD));
  1018.                 break;
  1019.             case 3:
  1020.                 elong(e->const);
  1021.                 break;
  1022.             default:
  1023.                 fatal("finish1");
  1024.                 }
  1025.             switch( e->odsiz ){
  1026.             case 0:        /* to allow An indirect w/ index */
  1027.             case 1:
  1028.                 break;  /* supressed */
  1029.             case 2:
  1030.                 eword(check(e->const2,SWORD));
  1031.                 break;
  1032.             case 3:
  1033.                 elong(e->const2);
  1034.                 break;
  1035.             default:
  1036.                 fatal("finish2");
  1037.                 }
  1038.             break;
  1039.         default:
  1040.             fatal("finish3");
  1041.             }
  1042.         break;
  1043.     case IMMED:
  1044.         if( Size == L )
  1045.             elong(e->const);
  1046.         else
  1047.             eword(e->const);        /* note: no range check here */
  1048.         break;
  1049.     case EXPR:
  1050.         if( e->siz==L )
  1051.             elong(e->const);
  1052.         else
  1053.             eword(check(e->const,SWORD));
  1054.         break;
  1055.     default:
  1056.         fatal("finish4");
  1057.         }
  1058. }
  1059.  
  1060. /*
  1061.  *      genxreg --- generate index register spec for indexed postword
  1062.  */
  1063. genxreg(e)
  1064. struct ea *e;
  1065. {
  1066.     int     wrd;
  1067.  
  1068.     wrd = e->stat2 ? 0x8000 : 0x0000 ;
  1069.     wrd += e->reg2<<12;
  1070.     if( e->siz == L )
  1071.         wrd += (1<<11);
  1072.     wrd += e->scl<<9;
  1073.     return(wrd);
  1074. }
  1075.  
  1076. /*
  1077.  *      getrlist --- return register list mask for an EA
  1078.  */
  1079. getrlist(e)
  1080. struct ea *e;
  1081. {
  1082.     int rlist;
  1083.  
  1084.     switch(e->type){
  1085.     case AN:        rlist = 1<<(e->reg + 8);break;
  1086.     case DN:        rlist = 1<< e->reg;    break;
  1087.     case RLIST:     rlist = e->reg;        break;
  1088.     default:        fatal("getrlist");
  1089.         }
  1090.     return( rlist );
  1091. }
  1092.  
  1093. /*
  1094.  *      bitfld --- return bit field extension word
  1095.  */
  1096. bitfld(e,r)
  1097. struct ea *e;
  1098. int r;
  1099. {
  1100.     int     offset,width;
  1101.  
  1102.     if( e->type != FIELD )
  1103.         fatal("Botch in bitfld");
  1104.  
  1105.     if( e->stat )
  1106.         offset = check(e->const,LOW5);
  1107.     else
  1108.         offset = e->reg + 0x20;
  1109.  
  1110.     if( e->stat2 )
  1111.         width = check(e->const2,LOW5);
  1112.     else
  1113.         width = e->reg2 + 0x20;
  1114.  
  1115.     return( (r<<12) + (offset<<6) + width );
  1116. }
  1117.  
  1118. char    *stypes[] = { "Symbol: ",  "Status:  ", "Data:   ", "Address: ", "Control: ",
  1119.               "Float:  ",  "Fcontrol:", "PCrel:  ", "ZPCrel:  ", "ZAddress:",
  1120.               "ZData:  ",  "Pmmu:    " };
  1121.  
  1122. /*
  1123.  *      dump_regs --- print reserved register names & classes
  1124.  */
  1125. dump_regs()
  1126. {
  1127.     register struct regs *r;
  1128.     int     lasttype = 999;
  1129.  
  1130.     printf("Reserved Register Names:");
  1131.     for(r=iregs; r<&iregs[NIREGS]; r++){
  1132.         if( isupper(r->r_name[0]))
  1133.             continue;       /* skip uppercase duplicate names */
  1134.         if( r->r_type != lasttype ){
  1135.             lasttype = r->r_type;
  1136.             printf("\n%s\t",stypes[lasttype]);
  1137.             }
  1138.         printf("%s ",r->r_name);
  1139.         }
  1140.     printf("\n\n");
  1141. }
  1142.  
  1143. /*
  1144.  *      do_opt --- scan operands and compare against list of options
  1145.  */
  1146. do_opt(l)
  1147. struct opts *l;
  1148. {
  1149.     char    opt[100];
  1150.     char    arg[100];
  1151.     char    *p,*q;
  1152.     struct opts *lp;
  1153.  
  1154.     q = opt;
  1155.     arg[0] = '\0';
  1156.     while( (p=next_str()) != NULL ){
  1157.         while(*p){
  1158.             if( *p == '=' ){
  1159.                 *q = '\0';
  1160.                 q = arg;
  1161.                 p++;
  1162.                 }
  1163.             else
  1164.                 *q++ = *p++;
  1165.             }
  1166.         *q = '\0';
  1167.         for(lp = l; lp->opt_name; lp++ ){
  1168.             if( strcmp(lp->opt_name,opt)==0){
  1169.                 (*lp->opt_func)(arg);
  1170.                 break;
  1171.                 }
  1172.             }
  1173.         if(lp->opt_name)
  1174.             serror("Unrecognized OPT: %s",opt);
  1175.         }
  1176. }
  1177.  
  1178. /* opt functions */
  1179. o_list(){ Lflag=1; }
  1180. o_nolist(){ Lflag=0; }
  1181. o_null(){}
  1182.  
  1183. #ifdef FLOAT
  1184. /*
  1185.  *      fsize --- return encoded size for floating point ea
  1186.  */
  1187. fsize()
  1188. {
  1189.     int sz;
  1190.  
  1191.     switch(Size){
  1192.     case L: sz = 0x0000; break;
  1193.     case S: sz = 0x0400; break;
  1194.     case X: sz = 0x0800; break;
  1195.     case P: sz = 0x0C00; break;
  1196.     case W: sz = 0x1000; break;
  1197.     case D: sz = 0x1400; break;
  1198.     case B: sz = 0x1800; break;
  1199. /*      case P: sz = 0x1C00; break;     not used? */
  1200.     default:
  1201.         fatal("Bad size in fsize");
  1202.         }
  1203.     return(sz);
  1204. }
  1205.  
  1206. /*
  1207.  *      checkfclist --- look for invalid fclist combinations
  1208.  *
  1209.  *      Dn addressing allowed on ea only if there is a single register
  1210.  *      in the list.  An addressing is allowed only if the single
  1211.  *      register FPIAR is specified.
  1212.  */
  1213. checkfclist(r,e)
  1214. int r;  /* register list */
  1215. struct ea *e;
  1216. {
  1217.     if( e->type == AN && (r&(FPCR|FPSR)) )
  1218.         error("An addressing allowed only on FPIAR");
  1219.     else if(e->type==DN ){
  1220.         if(r != FPCR && r != FPSR && r != FPIAR )
  1221.             error("Only a single FP ctrl. reg may be selected");
  1222.         }
  1223. }
  1224.  
  1225. o_fpid(s)
  1226. char *s;
  1227. {
  1228.     int id;
  1229.  
  1230.     if( *s ){
  1231.         id = atoi(s);
  1232.         if( id<0 || id>7 )
  1233.             error("Bad Co-processor id");
  1234.         else
  1235.             Fpid = id;
  1236.         }
  1237. }
  1238.  
  1239. o_round(s){}
  1240. o_prec(s){}
  1241. #endif
  1242.  
  1243. #ifdef PMMU
  1244. /*
  1245.  *      pmmu_fc --- return encoding for function code specifier
  1246.  */
  1247. pmmu_fc(e)
  1248. struct ea *e;
  1249. {
  1250.     int fc;
  1251.  
  1252.     if(e->type == EXPR )
  1253.         fc = 0x10 + check(e->const,LOW4);
  1254.     else if( e->type == DN )
  1255.         fc = 0x8 + e->reg;
  1256.     else if( e->type == CN && e->reg == SFC )
  1257.         fc = 0;
  1258.     else if( e->type == CN && e->reg == DFC )
  1259.         fc = 1;
  1260.     else
  1261.         error("Bad Func. Code specifier");
  1262.     return(fc);
  1263. }
  1264. #endif
  1265.  
  1266.